package com.fz.service.impl;

import com.aventrix.jnanoid.jnanoid.NanoIdUtils;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.fz.entity.Uploadfile;
import com.fz.mapper.UploadfileMapper;
import com.fz.service.UploadfileService;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import io.minio.MinioClient;
import io.minio.PutObjectArgs;
import io.minio.RemoveObjectArgs;
import io.minio.errors.*;
import org.apache.commons.io.FilenameUtils;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import org.springframework.util.DigestUtils;
import org.springframework.web.multipart.MultipartFile;

import java.io.IOException;
import java.security.InvalidKeyException;
import java.security.NoSuchAlgorithmException;

/**
 * <p>
 * 存储上传文件信息 服务实现类
 * </p>
 *
 * @author hyr
 * @since 2025-06-18
 */
@Service
public class UploadfileServiceImpl extends ServiceImpl<UploadfileMapper, Uploadfile> implements UploadfileService {
    @Value("${minio.config.endpoint}")
    private String endpoint;
    @Value("${minio.config.username}")
    private String username;
    @Value("${minio.config.password}")
    private String password;

    @Override
    public String upload(String bucket, MultipartFile file) throws IOException, ServerException, InsufficientDataException, ErrorResponseException, NoSuchAlgorithmException, InvalidKeyException, InvalidResponseException, XmlParserException, InternalException {
        long size=file.getSize();
        String contentType=file.getContentType();
        String md5= DigestUtils.md5DigestAsHex(file.getInputStream());
        Uploadfile uploadFile=this.get(md5, size, contentType);
        if(null!=uploadFile){
            return uploadFile.getPath();
        }
        System.out.println(file);
        MinioClient client = MinioClient.builder()
                .credentials(username, this.password)
                .endpoint(endpoint)
                .build();
        String filename= NanoIdUtils.randomNanoId() + "." + FilenameUtils.getExtension(file.getOriginalFilename());
        client.putObject(PutObjectArgs.builder()
                .bucket(bucket)
                .contentType(contentType)
                .stream(file.getInputStream(),size, 0)
                .object(filename)
                .build());
        final String path="/"+bucket+"/"+filename;
        uploadFile=new Uploadfile(md5,size,contentType,path);
        this.save(uploadFile);
        return path;
    }

    @Override
    public Uploadfile get(String md5, Long size, String contentType) {
        QueryWrapper<Uploadfile> wrapper = new QueryWrapper<>();
        wrapper.eq("md5", md5)
                .eq("size", size)
                .eq("content_type", contentType);
        return this.getOne(wrapper);
    }

    @Override
    public boolean delete(String bucket, String path) throws ServerException, InsufficientDataException, ErrorResponseException, NoSuchAlgorithmException, InvalidKeyException, InvalidResponseException, XmlParserException, InternalException, IOException {
        MinioClient client = MinioClient.builder()
                .credentials(username, this.password)
                .endpoint(endpoint)
                .build();

        // Extract the filename from the path
        String filename = path.substring(path.lastIndexOf("/") + 1);

        // Remove the object from Minio
        client.removeObject(RemoveObjectArgs.builder()
                .bucket(bucket)
                .object(filename)
                .build());

        // Remove the file record from the database
        QueryWrapper<Uploadfile> wrapper = new QueryWrapper<>();
        wrapper.eq("path", path);
        return this.remove(wrapper);
    }
}
